package annotation;

import java.lang.annotation.*;
import java.lang.reflect.Constructor;
import java.lang.reflect.Field;
import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;
import java.sql.SQLOutput;

/**
 * @Author: Miyako
 * @Date: 2024-07-23-14:20
 * @Description:
 */
public class AnnotationDemo01 {

    public static void main(String[] args) throws NoSuchFieldException, NoSuchMethodException, InvocationTargetException, IllegalAccessException {
        Class<MyClass> clazz = MyClass.class;
//        boolean s = clazz.isAnnotationPresent(MyAnnotation2.class);//判断是否是注解
//        System.out.println(s);
//        MyAnnotation2 m2 =  clazz.getAnnotation(MyAnnotation2.class);//获取注解
//        System.out.println(m2 instanceof Annotation);
//        Field sf = clazz.getDeclaredField("a");
//        sf.setAccessible(true);
//        boolean sss = sf.isAnnotationPresent(MyAnnotation3.class);
//        System.out.println(sss);
//        MyAnnotation3 m3 = sf.getAnnotation(MyAnnotation3.class);
//        //将值传入m3的value
//        Method sm = clazz.getMethod("setA", int.class);
////        sf.set(clazz,m3.value());
//
//        MyClass myClass = new MyClass();
//        Constructor<?>[] constructor = clazz.getDeclaredConstructors();
//        System.out.println(constructor==null);
//        sf.set(myClass,m3.value());
//        sm.invoke(myClass,m3.value());
//        System.out.println(myClass.getA());

        Method[] methods = clazz.getMethods();//获取所有方法
        for (Method method : methods) {
            if (method.isAnnotationPresent(MyAnnotation.class)) {
                System.out.println(method.getName() + "包含");
            } else System.out.println(method.getName() + "不包含");
        }
    }

}
//自定义一个注解，限定方法

@MyAnnotation2//
@Target({ElementType.METHOD, ElementType.TYPE, ElementType.CONSTRUCTOR})//限定注解的作用范围
@Retention(RetentionPolicy.RUNTIME)
@interface MyAnnotation {//自定义注解


}

@MyAnnotation2
@Target({ElementType.ANNOTATION_TYPE, ElementType.TYPE})//可以注解元注解
@Retention(RetentionPolicy.RUNTIME)//保留到运行时，可以通过反射获取注解
@interface MyAnnotation2 {
}

@Target({ElementType.FIELD})
@Retention(RetentionPolicy.RUNTIME)
@interface MyAnnotation3 {
    int value();
}


@MyAnnotation2//注解类
class MyClass {
    @MyAnnotation//注解构造方法
    public MyClass() {

    }

    @MyAnnotation//注解方法
    public void test(String a) {
    }


    @MyAnnotation3(100)//注解元素
    private int a;

    @MyAnnotation
    public void setA(int a) {
        this.a = a;
    }

    @MyAnnotation
    public int getA() {
        return a;
    }
}
